# -*- coding: utf-8 -*-
"""
Created on Sun Apr  7 23:28:50 2024

@author: 123
"""


import pandas as pd 
import numpy as np

# D:\360安全浏览器下载\购买银行产品数据集

bank_train_df = pd.read_csv(r'D:\360安全浏览器下载\购买银行产品数据集\train.csv')

###bank_test_df = pd.read_csv(r'D:\360安全浏览器下载\购买银行产品数据集\test.csv')




def dummy_variable_processing(col_name,source_df):
    dummy_df=pd.get_dummies(source_df[col_name], prefix=col_name)
    dummy_result_df=dummy_df.iloc[:,:-1]
    return dummy_result_df


#dummy_Gender = dummy_variable_processing(col_name='Gender',source_df=bank_train_df)

dummy_job =  dummy_variable_processing(col_name='job',source_df=bank_train_df)

dummy_marital=  dummy_variable_processing(col_name='marital',source_df=bank_train_df)
dummy_education=  dummy_variable_processing(col_name='education',source_df=bank_train_df)
dummy_poutcome=  dummy_variable_processing(col_name='poutcome',source_df=bank_train_df)

dummy_default=  dummy_variable_processing(col_name='default',source_df=bank_train_df)

dummy_housing=  dummy_variable_processing(col_name='housing',source_df=bank_train_df)
dummy_loan=  dummy_variable_processing(col_name='loan',source_df=bank_train_df)



bank_train_df['contact'] = bank_train_df['contact'].replace({'cellular': 1, 'telephone': 0})

#subscribe
bank_train_df['subscribe'] = bank_train_df['subscribe'].replace({'no': 0, 'yes': 1})

bank_train_df['month'] = bank_train_df['month'].replace({'jan':1,
'feb':2,
'mar':3,
'apr':4,
'may':5,
'jun':6,
'jul':7,
'aug':8,
'sep':9,
'oct':10,
'nov':11,
'dec':12})

bank_train_df['sin_month'] = np.sin(bank_train_df['month'] * 2 * np.pi / 12)
bank_train_df['cos_month'] = np.cos(bank_train_df['month'] * 2 * np.pi / 12)

bank_train_df['day_of_week'] = bank_train_df['day_of_week'].replace({
'mon':1,
'tue':2,
'wed':3,
'thu':4,
'fri':5,
'sat':6,
'sun':7})

bank_train_df['sin_day_of_week'] = np.sin(bank_train_df['day_of_week'] * 2 * np.pi / 7)
bank_train_df['cos_day_of_week'] = np.cos(bank_train_df['day_of_week'] * 2 * np.pi / 7)


bank_df = bank_train_df[['subscribe','age',  'contact', 'month', 'day_of_week', 'duration', 'campaign',
       'pdays', 'previous', 'emp_var_rate', 'cons_price_index',
       'cons_conf_index', 'lending_rate3m', 'nr_employed', 
       'sin_month', 'cos_month', 'sin_day_of_week', 'cos_day_of_week']]


bank_result = pd.concat([bank_df,dummy_job,dummy_marital,dummy_education,dummy_poutcome,dummy_default,dummy_housing,dummy_loan],axis=1)
print(bank_result.columns)

bank_train = bank_result.iloc[:20000,:]
bank_test  = bank_result.iloc[20000:,:]

bank_train = bank_train.reset_index(drop=True)
bank_test  = bank_test.reset_index(drop=True)

y_train = bank_train.iloc[:,:1]
x_train = bank_train.iloc[:,1:]

y_test = bank_test.iloc[:,:1]
x_test = bank_test.iloc[:,1:]

#划分训练集和测试集

from sklearn.metrics import classification_report, accuracy_score 
from sklearn.metrics import roc_auc_score,roc_curve,auc

# 调用逻辑 回归模型 
from sklearn.linear_model import LogisticRegression

clf_lr = LogisticRegression() #调用模型
clf_lr.fit(x_train,y_train) #训练模型

# 预测测试集的结果  
y_pred = clf_lr.predict(x_test)
# 使用测试集进行预测，得到预测概率
#y_pred_prob = clf_lr.predict_proba(x_test)[:, 1]

# 计算AUC值
#clf_lr_auc_score = roc_auc_score(y_test, y_pred_prob)


  
# 输出精确度、召回率和F1分数  
print(classification_report(y_test, y_pred))  

#朴素贝叶斯二项分布
import sklearn.naive_bayes as sk_bayes
from sklearn.metrics import classification_report


clf_bn_bin = sk_bayes.BernoulliNB(alpha=1.0,binarize=0.0,fit_prior=True,class_prior=None) #伯努利分布的朴素贝叶斯
clf_bn_bin.fit(x_train,y_train)

# 预测测试集的结果  
y_pred = clf_bn_bin.predict(x_test)  
#y_pred_prob = clf_bn_bin.predict_proba(x_test)[:, 1]

# 计算AUC值
#clf_bn_bin_auc_score = roc_auc_score(y_test, y_pred_prob)
  

# 输出精确度、召回率和F1分数  
print(classification_report(y_test, y_pred))  

#n朴素贝叶斯(二项分布)模型评价: 0.8697628738634753

clf_bn_gau = sk_bayes.GaussianNB()#高斯分布的朴素贝叶斯
clf_bn_gau.fit(x_train,y_train)

# 预测测试集的结果  
#y_pred = clf_bn_gau.predict(x_test)
#y_pred_prob = clf_bn_gau.predict_proba(x_test)[:, 1]

# 计算AUC值
#clf_bn_gau_auc_score = roc_auc_score(y_test, y_pred_prob)
  
# 输出精确度、召回率和F1分数  
print(classification_report(y_test, y_pred))  


#支持向量机（Support Vector Machine, SVM）:
#SVM可以有效地处理线性和非线性问题。通过使用不同的核函数，SVM可以在高维空间中找到最佳分割超平面。



from sklearn.svm import SVC
svc_model = SVC(probability=True)
#决策树（Decision Tree）:
#决策树是一种基本的分类和回归方法。它通过学习简单的决策规则推断出的树结构进行预测。
svc_model.fit(x_train,y_train)
# 预测测试集的结果  
y_pred = svc_model.predict(x_test)  
# 输出精确度、召回率和F1分数  
#print(classification_report(y_test, y_pred))  
#y_pred_prob = svc_model.predict_proba(x_test)[:, 1]

# 计算AUC值
#svc_model_auc_score = roc_auc_score(y_test, y_pred_prob)
print(classification_report(y_test, y_pred))  

from sklearn.tree import DecisionTreeClassifier
dtc_model = DecisionTreeClassifier()
dtc_model.fit(x_train,y_train)
# 预测测试集的结果  
y_pred = dtc_model.predict(x_test)  
# 输出精确度、召回率和F1分数  
#print(classification_report(y_test, y_pred))
#y_pred_prob = dtc_model.predict_proba(x_test)[:, 1]
print(classification_report(y_test, y_pred))  
# 假设我们关注的是类别1的预测概率
# 计算AUC值
#dtc_model_auc_score = roc_auc_score(y_test, y_pred_prob)

#随机森林（Random Forest）:
#随机森林是一种集成学习方法，通过构建多个决策树并将它们的预测结果进行投票或平均来提高预测准确性。
"""
from sklearn.ensemble import RandomForestClassifier
rfc_model = RandomForestClassifier(probability=True)
rfc_model.fit(x_train,y_train)
# 预测测试集的结果  
y_pred = rfc_model.predict(x_test)  
# 输出精确度、召回率和F1分数  
print(classification_report(y_test, y_pred))  
#梯度提升树（Gradient Boosting Trees）:
#梯度提升树是另一种集成学习方法，通过逐步添加树来纠正前一个模型的错误。
"""
from sklearn.ensemble import GradientBoostingClassifier
gbc_model = GradientBoostingClassifier()

gbc_model.fit(x_train,y_train)
# 预测测试集的结果  
y_pred = gbc_model.predict(x_test)
#y_pred_prob = gbc_model.predict_proba(x_test)[:, 1]
print(classification_report(y_test, y_pred)) 
# 假设我们关注的是类别1的预测概率
# 计算AUC值
#gbc_model_auc_score = roc_auc_score(y_test, y_pred_prob)
# 输出精确度、召回率和F1分数  
#print(classification_report(y_test, y_pred)) 
#K-近邻（K-Nearest Neighbors, KNN）:
#KNN是一种基于实例的学习或非泛化学习，它根据最近的K个邻居的类别来预测新数据点的类别。

from sklearn.neighbors import KNeighborsClassifier
knn_model = KNeighborsClassifier()
knn_model.fit(x_train,y_train)
# 预测测试集的结果  
y_pred = knn_model.predict(x_test)  
#y_pred_prob = knn_model.predict_proba(x_test)[:, 1]
print(classification_report(y_test, y_pred)) 
# 假设我们关注的是类别1的预测概率
# 计算AUC值
#knn_model_auc_score = roc_auc_score(y_test, y_pred_prob)
# 输出精确度、召回率和F1分数  
#print(classification_report(y_test, y_pred)) 
#scikit-learn提供了一个多层感知机（MLP）类，可以用来构建简单的神经网络。
from sklearn.neural_network import MLPClassifier
mlp_model = MLPClassifier()
mlp_model.fit(x_train,y_train)
# 预测测试集的结果  
y_pred = mlp_model.predict(x_test)
#y_pred_prob = mlp_model.predict_proba(x_test)[:, 1]
print(classification_report(y_test, y_pred)) 
# 假设我们关注的是类别1的预测概率
# 计算AUC值
#mlp_model_auc_score = roc_auc_score(y_test, y_pred_prob)
# 输出精确度、召回率和F1分数  
#print(classification_report(y_test, y_pred)) 





#https://blog.csdn.net/ylqDiana/article/details/118764019
#多条ROC曲线绘制函数
import matplotlib.pyplot as plt
from matplotlib.font_manager import FontProperties
import matplotlib
matplotlib.rcParams['font.family'] = 'Microsoft YaHei'
def multi_models_roc(names, sampling_methods, colors, x_test, y_test, save=True, dpin=100):
        """
        将多个机器模型的roc图输出到一张图上
        
        Args:
            names: list, 多个模型的名称
            sampling_methods: list, 多个模型的实例化对象
            save: 选择是否将结果保存（默认为png格式）
            
        Returns:
            返回图片对象plt
        """

        plt.figure(figsize=(20, 20), dpi=dpin)

        for (name, method, colorname) in zip(names, sampling_methods, colors):
            
            y_test_preds = method.predict(x_test)
            y_test_predprob = method.predict_proba(x_test)[:,1]
            fpr, tpr, thresholds = roc_curve(y_test, y_test_predprob, pos_label=1)
            
            plt.plot(fpr, tpr, lw=5, label='{} (AUC={:.3f})'.format(name, auc(fpr, tpr)),color = colorname)
            plt.plot([0, 1], [0, 1], '--', lw=5, color = 'grey')
            plt.axis('square')
            plt.xlim([0, 1])
            plt.ylim([0, 1])
            plt.xlabel('False Positive Rate',fontsize=20)
            plt.ylabel('True Positive Rate',fontsize=20)
            plt.title('不同模型的ROC曲线',fontsize=25)
            plt.legend(loc='lower right',fontsize=20)

        if save:
            plt.savefig('multi_models_roc.png')
            
        return plt
    
    
    

#调用方法时，需要把模型本身（如clf_xx）、模型名字(如GBDT)和对应颜色（如crimson）按照顺序、以列表形式传入函数作为参数。
"""
names = ['Logistic Regression',
         'Random Forest',
         'XGBoost',
         'AdaBoost',
         'GBDT',
         'LGBM']



sampling_methods = [clf_lr,
                    clf_rf,
                    clf_xgb,
                    clf_adb,
                    clf_gbdt,
                    clf_lgbm
                   ]
# name 'clf_lr' is not defined

colors = ['crimson',
          'orange',
          'gold',
          'mediumseagreen',
          'steelblue', 
          'mediumpurple'  
         ]
"""

names = ['Logistic Regression',
         'sk_bayes BernoulliNB',
         'sk_bayes GaussianNB',
         'Support Vector Machine',
         'Decision Tree Classifier',
         #'Random Forest Classifier',
         'Gradient Boosting Classifier',
         'KNeighbors Classifier',
         'MLP Classifier'
         ]

sampling_methods = [clf_lr,
                    clf_bn_bin,
                    clf_bn_gau,
                    
                    svc_model,
                    dtc_model,
                   # rfc_model,
                    gbc_model,
                    knn_model,
                    mlp_model
                   ]

has_predict_proba = hasattr(svc_model, 'predict_proba')  
print(has_predict_proba)  # 如果输出 True，则表示有该方法

#'red', 'blue', 'green', 'yellow', 'cyan', 'magenta', 'black', 'white' 
colors = ['crimson',
          'orange',
          'gold',
          'red',
          'blue', 
          #'green', 
          'yellow', 
          'cyan', 
          'magenta'
         ]

#ROC curves

import matplotlib.pyplot as plt
train_roc_graph = multi_models_roc(names, sampling_methods, colors, x_train, y_train, save = True)
train_roc_graph.savefig('ROC_Train_all.png')

"""

import matplotlib.pyplot as plt

# 假设你有以下模型的AUC值
models = ['lr_model', 'bn_bin_model', 'bn_gau_model', 'svc_model','dtc_model','gbc_model','knn_model','mlp_model']
auc_values = [clf_lr_auc_score,
              clf_bn_bin_auc_score,
              clf_bn_gau_auc_score,
              svc_model_auc_score,
              dtc_model_auc_score,
              gbc_model_auc_score,
              knn_model_auc_score,
              mlp_model_auc_score]

# 创建一个条形图
plt.figure(figsize=(10, 6))  # 设置图形的大小
plt.plot(models, auc_values, color='skyblue', alpha=0.7)
"""